<markup>
<section data-view-id = "page1">
	<header>视图1</header>
	<h1>这是视图1</h1>
	<div data-view-rel = "page2" class = "btn">进入视图2</div>
</section>
<section data-view-id = "page2">
	<header>
		<span class = "nav-back" data-view-rel = ":back"></span>视图2
	</header>
	<h1>这是视图2</h1>
	<div data-view-rel = "page3" data-view-rel-type="change" class = "btn">进入视图2</div>
</section>
<section data-view-id = "page3">
	<header>
		<span class = "nav-back" data-view-rel = ":back"></span>视图3
	</header>
	<h1>这是视图3</h1>
</section>
</markup>
<link rel = "stylesheet" href = "demo/css/common.css"/>
<style>
/**
 * 定义动画
 */
@keyframes fadeIn{
	from{opacity: 0;}
	to{opacity: 1;}
}
@keyframes fadeOut{
	from{opacity: 1;}
	to{opacity: 0;}
}
@keyframes hideToLeft{
	from{transform: translate3d(0, 0, 0); opacity: 1;}
	to{transform: translate3d(-50%, 0, 0); opacity: 1;}
}
@keyframes showFromRight{
	from{transform: translate3d(100%, 0, 0); opacity: 1;}
	to{transform: translate3d(0, 0, 0); opacity: 1;}
}
@keyframes hideToRight{
	from{transform: translate3d(0, 0, 0); opacity: 1;}
	to{transform: translate3d(100%, 0, 0); opacity: 1;}
}
@keyframes showFromLeft{
	from{transform: translate3d(-50%, 0, 0); opacity: 1;}
	to{transform: translate3d(0, 0, 0); opacity: 1;}
}

/**
 * 视图容器水平居中
 */
*[data-view-container]{
	position: relative;
	visibility: hidden;
	margin: 0 auto;
	overflow: hidden;
	transition: height ease 0.5s;
}
*[data-view-container][data-view-state=ready]{
	visibility: visible;
}
/**
 * 所有视图重叠在一起，默认都不显示
 */
*[data-view=true] {
	display: block;
	opacity: 0;
	z-index: 0;
	position: absolute;
	left: 0;
	top: 0;
	width: 100%;
	height: 100%;
	box-sizing: border-box;
	overflow: auto;
	-webkit-overflow-scrolling: touch;
	background: #F3F3F3;
	box-shadow: 0 0 70px rgba(0, 0, 0, 0.3);
}
/**
 * 视图隐藏时要呈现的半透明黑色蒙层。默认不显示
 */
*[data-view=true]:before{
	opacity: 0;
	content: "";
	display: none;
	position: absolute;
	left: 0;
	top: 0;
	width: 100%;
	height: 100%;
	background: rgba(0, 0, 0, 0.3);
}
/**
 * 活动视图可见
 */
*[data-view=true].active {
	opacity: 1;
	z-index: 1;
}

/**
 * 有条件地引用动画
 */
.view.fadeIn{
	animation: fadeIn 0.6s ease-out;
}
.view.fadeOut{
	animation: fadeOut 0.6s ease-out;
}

/* 视图含有hideToLeft样式类时播放hideToLeft动画 */
.view.hideToLeft{
	animation: hideToLeft 0.6s ease-out;
}
/* 视图向左隐藏时逐渐显示半透明黑色蒙层 */
.view.hideToLeft:before{
	display: block;
	animation: fadeIn 0.6s linear;
}

/* 视图含有showFromLeft样式类时播放showFromLeft动画 */
.view.showFromLeft{
	animation: showFromLeft 0.6s ease-out;
}
/* 视图取消隐藏时逐渐关闭半透明黑色蒙层 */
.view.showFromLeft:before{
	display: block;
	animation: fadeOut 0.6s linear;
}

/**
 * 视图含有hideToRight样式类时播放hideToRight动画。
 * z-index要比活动视图的1更高，从而使其不会被活动视图覆盖
 */
.view.hideToRight{
	z-index: 2;
	animation: hideToRight 0.6s ease-out;
}

/* 视图含有showFromRightn样式类时播放showFromRightn动画 */
.view.showFromRight{
	animation: showFromRight 0.6s ease-out;
}
</style>
<script>
var timer;

/**
 * 动画持续时长，需要与css中定义的动画时长一致
 * @type {number}
 */
var animationDuration = 600;

/**
 * 清除给定DOM元素上声明的动画样式
 * @param {HTMLElement} obj
 */
var clear = function(obj){
	if(!obj)
		return;

	"fadeIn, fadeOut, hideToLeft, showFromRight, hideToRight, showFromLeft".split(/\s*,\s*/).forEach(function(className){
		util.removeClass(obj, className);
	});
};

/**
 * param {Object} meta 切换操作的元数据描述
 * @param {HTMLElement} meta.srcElement 视图切换时，要离开的当前视图对应的DOM元素。可能为null
 * @param {HTMLElement} meta.tarElement 视图切换时，要进入的目标视图对应的DOM元素
 * @param {String} meta.type 视图切换方式
 * @param {Function} meta.render 渲染句柄
 */
View.setSwitchAnimation(function(meta){
	var srcElement = meta.srcElement,
		tarElement = meta.targetElement,
		type = meta.type,
		trigger = meta.trigger,
		render = meta.render;

	/**
	 * 动画播放前清除可能存在的动画样式
	 */
	clear(srcElement);
	clear(tarElement);

	/**
	 * 调用View.js传递而来的渲染句柄，完成活动视图的切换，包括：
	 * 1. 视图参数的传递
	 * 2. 活动视图样式类的切换
	 * 3. leave，ready、enter等事件的触发
	 */
	render();

	var isNav = type === View.SWITCHTYPE_VIEWNAV,
		isChange = type === View.SWITCHTYPE_VIEWCHANGE,
		isHistoryBack = type === View.SWITCHTYPE_HISTORYBACK,
		isHistoryForward = type === View.SWITCHTYPE_HISTORYFORWARD;

	/**
	 * 视图切换动作是“替换堆栈”的方式，或浏览器不支持对history的操作
	 */
	if(!View.checkIfBrowserHistorySupportsPushPopAction() || isChange){
		util.addClass(srcElement, "fadeOut");
		util.addClass(tarElement, "fadeIn");
	}else if(isHistoryForward || isNav){
		/**
		 * 视图切换动作是“压入堆栈”的方式（浏览器前进，或代码触发）
		 */

		util.addClass(srcElement, "hideToLeft");
		util.addClass(tarElement, "showFromRight");
	}else{
		/**
		 * 视图切换动作是“弹出堆栈”的方式（浏览器后退）
		 */

		util.addClass(srcElement, "hideToRight");
		util.addClass(tarElement, "showFromLeft");
	}

	/**
	 * 动画播放完成后清除动画样式
	 */
	clearTimeout(timer);
	timer = setTimeout(function(){
		clear(srcElement);
		clear(tarElement);
	}, animationDuration);
});
</script>